package bit.lotterysystem.service.activityStatus.impl;

import bit.lotterysystem.common.errorcode.ServiceErrorCodeConstants;
import bit.lotterysystem.common.exception.ServiceException;
import bit.lotterysystem.service.ActivityService;
import bit.lotterysystem.service.activityStatus.ActivityStatusManager;
import bit.lotterysystem.service.activityStatus.operater.AbstractActivityOperater;
import bit.lotterysystem.service.dto.ConvertActivityStatusDTO;

import bit.lotterysystem.service.impl.ActivityServiceImpl;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

@Service
public class ActivityStatusManagerImpl implements ActivityStatusManager {

    private static final Logger logger= LoggerFactory.getLogger(ActivityServiceImpl.class);
    @Autowired
    private final Map<String, AbstractActivityOperater> operaterMap=new HashMap<>();
    @Autowired
    private ActivityService activityService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void handlerEvent(ConvertActivityStatusDTO convertActivityStatusDTO) {

        if(CollectionUtils.isEmpty(operaterMap)){
            logger.warn("operaterMap为空！");
            return;
        }
        //map:<String,AbstractActivityOperater>
        Map<String,AbstractActivityOperater> currMap=new HashMap<>(operaterMap);

        Boolean update=false;
        //先处理：人员、奖品
        update=processConvertStatus(convertActivityStatusDTO,currMap,1);
        //后处理：活动
//        if(update){
//            processConvertStatus(convertActivityStatusDTO,currMap,2);
//        }else{
//            update=processConvertStatus(convertActivityStatusDTO,currMap,2);
//        }
        update=processConvertStatus(convertActivityStatusDTO,currMap,2)||update;


        //更新缓存
        if(update){
            activityService.cacheActivity(convertActivityStatusDTO.getActivityId());
        }
    }

    @Override
    public void rollbackHandlerEvent(ConvertActivityStatusDTO convertActivityStatusDTO) {
        //operatormap:活动、奖品、人员
        //活动一定没有完成，是running
        //活动一定要回滚，因为奖品回滚了，一定没有抽完
        for(AbstractActivityOperater operater : operaterMap.values()){
            operater.convert(convertActivityStatusDTO);
        }
        //更新缓存
        activityService.cacheActivity(convertActivityStatusDTO.getActivityId());

    }

    /**
     * 扭转状态
     * @param convertActivityStatusDTO
     * @param currMap
     * @param sequence
     * @return
     */
    private Boolean processConvertStatus(ConvertActivityStatusDTO convertActivityStatusDTO,
                                         Map<String, AbstractActivityOperater> currMap,
                                         int sequence) {

        Boolean update=false;
        //遍历currMap
        Iterator<Map.Entry<String, AbstractActivityOperater>> iterator=currMap.entrySet().iterator();
        while(iterator.hasNext()){
            AbstractActivityOperater operater=iterator.next().getValue();
            //Operater是否需要转换
            if(operater.sequence()!=sequence
                    ||!operater.needConvert(convertActivityStatusDTO)){
                continue;
            }
            //需要转换：转换
            if(!operater.convert(convertActivityStatusDTO)){
                logger.error("{}状态转换失败！",operater.getClass().getName());
                throw new ServiceException(ServiceErrorCodeConstants.ACTIVITY_STATUS_CONVERT_ERROR);
            }
            //currMap删除当前operater
            iterator.remove();
            update=true;
        }

        //返回
        return update;
    }
}
